/*
 * IndiceInvertido.cpp
 *
 *  Created on: 25/09/2011
 *      Author: emma
 */

#include "IndiceInvertido.h"

IndiceInvertido::IndiceInvertido() {
	this->arbol = new DAWG();
	this->archivoIndice = new ArchivoIndice("ArchivoRI");
	this->archivoLexico = new ArchivoLexico("ArchivoLexico");
}

IndiceInvertido::~IndiceInvertido() {
	delete this->arbol;

}

void IndiceInvertido::agregarRegistro(string termino, RegistroIndice* unRegistroIndice){
	//Inserto en el arbol el termino del nuevo registro indice a agregar
	this->arbol->agregarPalabra(termino);

	//Obtengo el nodo correspondiente al nuevo termino insertado y le agrego su correspondiente registro indice
	DAWGNodeEnd* nodo = (DAWGNodeEnd*) arbol->obtenerPalabra(termino);

	nodo->setInfo(unRegistroIndice);
}

//Este metodo sirve para la etapa de indexacion
RegistroIndice* IndiceInvertido::obtenerRegistro(string termino){
	//Busco el termino en el arbol y obtengo el nodo correspondiente al termino
	DAWGNodeEnd* nodo = (DAWGNodeEnd*) this->arbol->obtenerPalabra(termino);

	//Devuelvo el registro correspondiente al nodo
	return (RegistroIndice*) (nodo->getInfo());
}

//Este metodo sirve para la etapa de busqueda
RegistroIndice* IndiceInvertido::obtenerRegistroIndice(string termino){
	//Busco el termino en el arbol y obtengo el nodo correspondiente al termino
	DAWGNodeEnd* nodo = (DAWGNodeEnd*) this->arbol->obtenerPalabra(termino);

	//Devuelvo el registro correspondiente al nodo
	RegistroId* unRegistroId = (RegistroId*) (nodo->getInfo());

	this->archivoIndice->abrirParaLeer();
	RegistroIndice* unRegistroIndice = this->archivoIndice->leer(unRegistroId->obtenerId());
	this->archivoIndice->cerrar();
	return unRegistroIndice;
}


bool IndiceInvertido::esta(string termino){
	//Busco el termino en el arbol y obtengo el nodo correspondiente al termino
	DAWGNodeEnd* nodo = (DAWGNodeEnd*) this->arbol->obtenerPalabra(termino);

	if(nodo != NULL)
		return true;
	else
		return false;
}

void IndiceInvertido::almacenar(){
	cout << "almacenando indice" << endl;
	list<string> *lexico = new list<string>();
	list<RegistroInfo*> *regInfo = new list<RegistroInfo*>();
	this->arbol->inorden(lexico, regInfo);

	this->archivoLexico->sobreescribir();
	this->archivoLexico->abrirParaEscribir();

	this->archivoIndice->sobreescribir();
	this->archivoIndice->abrirParaEscribir();

	list<string>::iterator itLexico = lexico->begin();
	list<RegistroInfo*>::iterator itRegInd = regInfo->begin();

	while(itLexico != lexico->end() && itRegInd != regInfo->end()){
		RegistroIndice *unRegistroIndice = (RegistroIndice*) (*itRegInd);
		int idRI = archivoIndice->escribir(unRegistroIndice);
		RegistroLexico* registroLexico = new RegistroLexico(*itLexico, idRI);
		archivoLexico->escribir(registroLexico);
		itLexico++;
		itRegInd++;
	}

	archivoLexico->cerrar();
	archivoIndice->cerrar();
}

void IndiceInvertido::cargar(){

	archivoLexico->abrirParaLeer();
	RegistroLexico *unRegLexico = archivoLexico->leer(0);

	while(unRegLexico != NULL){
		this->arbol->agregarPalabra(unRegLexico->obtenerLexico());
		RegistroId* unRI = new RegistroId(unRegLexico->obtenerId());
		this->arbol->obtenerPalabra(unRegLexico->obtenerLexico())->setInfo(unRI);
		unRegLexico = archivoLexico->leerSiguiente();
	}

	archivoLexico->cerrar();

}

void IndiceInvertido::destruir(){
	delete this->arbol;
	this->arbol = new DAWG();
	this->archivoIndice->sobreescribir();
	this->archivoLexico->sobreescribir();
}
